package com.jjc.android.activity

import android.content.Context
import android.content.Intent
import android.os.Bundle
import android.widget.TextView
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView
import com.github.gzuliyujiang.wheelpicker.DatePicker
import com.github.gzuliyujiang.wheelpicker.annotation.DateMode
import com.github.gzuliyujiang.wheelpicker.entity.DateEntity
import com.haibin.calendarview.Calendar
import com.haibin.calendarview.CalendarLayout
import com.haibin.calendarview.CalendarView
import com.haibin.calendarview.CalendarView.*
import com.hjq.toast.ToastUtils
import com.jjc.android.Constants
import com.jjc.android.R
import com.jjc.android.UserManager
import com.jjc.android.adapter.HealthRecordAdapter
import com.jjc.android.base.BaseActivity
import com.jjc.android.dialog.AttachListDialog
import com.jjc.android.dialog.MessageImageDialog
import com.jjc.android.entity.*
import com.jjc.android.net.SimpleHttpCallback
import com.jjc.android.util.Common
import com.jjc.android.util.MultiLanguageUtil
import com.jjc.android.util.paramEx
import com.jjc.android.view.formatTwo
import com.jjc.android.view.onClick
import com.lxj.xpopup.enums.PopupPosition
import com.lzy.okgo.OkGo
import com.zerobranch.layout.SwipeLayout
import org.greenrobot.eventbus.EventBus
import kotlin.properties.Delegates


class HealthRecordsActivity : BaseActivity(), OnCalendarSelectListener, OnYearChangeListener{

    companion object{
        fun start(context:Context,primaryClassifyId:String,secondaryClassifyId:String,testerId:String?){
            val intent = Intent(context,HealthRecordsActivity::class.java)
            intent.putExtra("primaryClassifyId",primaryClassifyId)
            intent.putExtra("secondaryClassifyId",secondaryClassifyId)
            intent.putExtra("testerId",testerId)
            context.startActivity(intent)
        }
    }

    override val layoutId: Int = R.layout.activity_health_records
    private val recyclerView: RecyclerView by lazy { findViewById(R.id.recyclerView) }
    private val calendarView: CalendarView by lazy { findViewById<CalendarView>(R.id.calendarView) }
    private val monthTxt: TextView by lazy { findViewById<TextView>(R.id.monthTxt) }
    private val yearTxt: TextView by lazy { findViewById<TextView>(R.id.yearTxt) }
    private val productTxt: TextView by lazy { findViewById<TextView>(R.id.productTxt) }
    private val userNameTxt: TextView by lazy { findViewById<TextView>(R.id.userNameTxt) }
    private var primaryClassifyId:String = ""
    private var secondaryClassifyId:String = ""
    private var testerId:String? = null
    private lateinit var adapter:HealthRecordAdapter

    private val chooseDateDialog by lazy {
        val picker = DatePicker(this)
        picker.wheelLayout.setDateLabel(getString(R.string.year_txt),getString(R.string.month_txt),"")
        picker.wheelLayout.setDateMode(DateMode.YEAR_MONTH)
        picker.wheelLayout.setRange(
            DateEntity.target(calendarView.minRangeCalendar.parseCalendar()),
            DateEntity.target(calendarView.maxRangeCalendar.parseCalendar())
        )
        picker.setOnDatePickedListener { year, month, day ->
            calendarView.scrollToCalendar(year,month, day)
        }
        picker
    }

    private var currentTester:TestedPersonDto? by Delegates.observable(null){ _, old, new->
        if(old?.id==new?.id) return@observable
        if(new==null){
            userNameTxt.text = getString(R.string.un_add_txt)
        }else{
            userNameTxt.text = new.provideText()
        }
        cleanCache()
        fetchRecords()
    }

    private var currentClassifyDto:SecondaryClassifyDto? by Delegates.observable(null){_,oldValue,newValue->
        if(oldValue?.id == newValue?.id) return@observable
        productTxt.text = newValue?.provideText()
        cleanCache()
        fetchRecords()
    }

    private var yearMonthPair:VarPair<Int,Int> = VarPair{
        yearTxt.text = String.format("%d%s",it.first,getString(R.string.year_txt))
        monthTxt.text = String.format("%d%s",it.second,getString(R.string.month_txt))
        fetchRecords()
    }

    override fun initView(savedInstanceState: Bundle?) {
        setActivityTitle(getString(R.string.health_docu_txt))
        recyclerView.layoutManager = LinearLayoutManager(this)
        adapter = HealthRecordAdapter()
        adapter.setOnItemChildClickListener { _, view, position ->
            val info = adapter.getItem(position)?:return@setOnItemChildClickListener
            when(view.id){
                R.id.right_view->{
                    (view.parent as? SwipeLayout)?.close(true)
                    MessageImageDialog.Builder(this)
                        .okClick {
                            OkGo.post<LzyResponse<Any>>(Constants.deleteFormRow)
                                .paramEx(mutableMapOf("rowid" to info.detectionId,"formheaduuid" to "2bc5b9902eee4a2699f44b689784f27e"),true)
                                .tag(this@HealthRecordsActivity)
                                .execute(object : SimpleHttpCallback<LzyResponse<Any>>(activity = this@HealthRecordsActivity){
                                    override fun onCallSuccess(response: LzyResponse<Any>) {
                                        ToastUtils.show(getString(R.string.remove_success_txt))
                                        fetchRecords()
                                        EventBus.getDefault().post(HealthRecordChangeEvent())
                                    }
                                })
                        }
                        .build()
                        .show()
                }
                else->DetectionReportActivity.start(this,info.detectionId)
            }

        }
        recyclerView.adapter = adapter

        calendarView.setWeekStarWithMon()
        calendarView.setOnCalendarSelectListener(this)
        calendarView.setOnYearChangeListener(this)
        yearMonthPair.putData(calendarView.curYear,calendarView.curMonth)
        yearTxt.onClick {
            showChooseDateDialog()
        }
        monthTxt.onClick {
            showChooseDateDialog()
        }
        userNameTxt.onClick {
            AttachListDialog<TestedPersonDto>(userNameTxt)
                .popupPosition(PopupPosition.Right)
                .contentList(testedPersonList)
                .onItemClick { _, value ->
                    currentTester = value
                }
                .build()
                .show()
        }
        productTxt.onClick {
            AttachListDialog<SecondaryClassifyDto>(productTxt)
                .popupPosition(PopupPosition.Right)
                .contentList(secondaryClassifyList)
                .onItemClick { _, value ->
                    currentClassifyDto = value
                }
                .build()
                .show()
        }
        showLoadingView(recyclerView)
        fetchPageInfo()
    }
    private val map: MutableMap<String, Calendar?> = HashMap()
    private val recordsMap: MutableMap<String, List<HealthRecordCalendarDto>?> = HashMap()

    private fun cleanCache(){
        map.clear()
        recordsMap.clear()
        calendarView.setSchemeDate(map)
    }

    private fun fetchRecords(){
        val pair = yearMonthPair?:return
        val tester = currentTester?:return
        val classify = currentClassifyDto?:return
        OkGo.post<LzyResponse<List<HealthRecordCalendarDto>>>(Constants.getHealthRecordDetails)
            .paramEx(mutableMapOf(
                "tuoTuUserId" to UserManager.userId(),
                "tuoTuToken" to UserManager.userInfo().tuoTuToken,
                "detectionUserId" to tester.id,
                "minorTermId" to classify.id,
                "collectStartDate" to String.format("%d-%s-%s",pair.first,pair.second.formatTwo(),1.formatTwo()),
                "collectEndDate" to String.format("%d-%s-%s",pair.first,pair.second.formatTwo(),Common.getDays(pair.first,pair.second).formatTwo())
            ))
            .tag(this)
            .execute(object : SimpleHttpCallback<LzyResponse<List<HealthRecordCalendarDto>>>(){
                override fun onCallSuccess(response: LzyResponse<List<HealthRecordCalendarDto>>) {
                    if(response.data?.isNullOrEmpty()==true){
                        showEmptyView()
                    }else{
                        recordsMap[String.format("%d-%s",pair.first,pair.second.formatTwo())] = response.data
                        hideLoadingView()
                        response.data?.forEach { info->
                            Common.parseFormat(info.collectDate,Common.yymmdd2)?.let { date->
                                getSchemeCalendar(date.get(java.util.Calendar.YEAR), date.get(java.util.Calendar.MONTH)+1, date.get(java.util.Calendar.DATE), -0xbf24db, "假")
                            }?.let {
                                map[it.toString()] = it
                            }
                        }
                        calendarView.setSchemeDate(map)
                        showCurrentDayRecord()
                    }
                }

                override fun onCallError(error: String?) {
                    super.onCallError(error)
                    showErrorView(error)
                }
            })
    }

    private fun showCurrentDayRecord(){
        calendarView.selectedCalendar.let { calendar->
            val target = String.format("%d-%s-%s",calendar.year,calendar.month.formatTwo(),calendar.day.formatTwo())
            recordsMap[String.format("%d-%s",calendar.year,calendar.month.formatTwo())].let { list->
                if(list.isNullOrEmpty()){
                    null
                }else{
                    list.find { info->
                        info.collectDate==target
                    }
                }
            }
        }.let {
            if(it==null||it.detectionDetails.isNullOrEmpty()){
                showEmptyView()
            }else{
                adapter.setNewData(it.detectionDetails)
                hideLoadingView()
            }
        }

    }

    private val testedPersonList = ArrayList<TestedPersonDto>()
    private val secondaryClassifyList = ArrayList<SecondaryClassifyDto>()
    override fun fetchPageInfo() {
        OkGo.post<LzyResponse<PageInfo<TestedPersonDto>>>(Constants.getFormList)
            .paramEx(mutableMapOf("page" to 1,"pagesize" to 100,"needpage" to 0,"formheaduuid" to "83ed64e98f6c4edbaf7b388d7691e57b","filters" to listOf<KeyValuePair>(
                KeyValuePair("61xugqtzoyid5pw2",UserManager.userId())
            )),true)
            .tag(this)
            .execute(object : SimpleHttpCallback<LzyResponse<PageInfo<TestedPersonDto>>>(false){
                override fun onCallSuccess(response: LzyResponse<PageInfo<TestedPersonDto>>) {
                    response.data?.data?.let {
                        testedPersonList.clear()
                        testedPersonList.addAll(it)
                    }
                    if(!testedPersonList.isNullOrEmpty()){
                        currentTester = if(testerId.isNullOrEmpty()){
                            testedPersonList[0]
                        }else{
                            testedPersonList.find { it.id == testerId }
                        }
                    }
                }

                override fun onCallError(error: String?) {
                    super.onCallError(error)
                }
            })
        OkGo.post<LzyResponse<PageInfo<SecondaryClassifyDto>>>(Constants.getFormList)
            .paramEx(mutableMapOf(
                "page" to 1,
                "pagesize" to 100,
                "needpage" to "1",
                "formheaduuid" to "0f078bd3ef0946548f6e18b1f245f8c3",
                "isasc" to true,
                "sortid" to "wfwx0dlcvkpojft1",
                "filters" to listOf<KeyValuePair>(
                    KeyValuePair("jysnwnlyigidwpaf",primaryClassifyId),
                    KeyValuePair("zxrqekxhvs1pdyik",MultiLanguageUtil.getInstance().getValue("1a36aa83-fec3-40c6-82e7-f5256dd23ca0","439d966f-54f5-42f0-94ad-f4df2801701a")),
                    KeyValuePair("gwkora0c5jwdubgf","9c6bbabb-d61b-43e8-936f-6d8330b76b85")
                )),true)
            .tag(this)
            .execute(object : SimpleHttpCallback<LzyResponse<PageInfo<SecondaryClassifyDto>>>(false){
                override fun onCallSuccess(response: LzyResponse<PageInfo<SecondaryClassifyDto>>) {
                    response.data?.data?.let {
                        secondaryClassifyList.clear()
                        secondaryClassifyList.addAll(it)
                    }
                    if(!secondaryClassifyList.isNullOrEmpty()){
                        currentClassifyDto = secondaryClassifyList.find { it.id == secondaryClassifyId }
                    }
                }

                override fun onCallError(error: String?) {
                    super.onCallError(error)
                }
            })
    }




    private fun getSchemeCalendar(
        year: Int,
        month: Int,
        day: Int,
        color: Int,
        text: String
    ): Calendar? {
        val calendar = Calendar()
        calendar.year = year
        calendar.month = month
        calendar.day = day
        calendar.schemeColor = color //如果单独标记颜色、则会使用这个颜色
        calendar.scheme = text
        return calendar
    }
    
    private fun showChooseDateDialog(){
        chooseDateDialog.wheelLayout.setDefaultValue(DateEntity.target(calendarView.selectedCalendar.parseCalendar()))
        chooseDateDialog.show()
    }

    override fun onCalendarOutOfRange(calendar: Calendar?) {

    }

    override fun onCalendarSelect(calendar: Calendar?, isClick: Boolean) {
        if(calendar?.year!=yearMonthPair.first||calendar?.month!=yearMonthPair.second){
            yearMonthPair.putData(calendar?.year,calendar?.month)
        }
        showCurrentDayRecord()
    }

    override fun onYearChange(year: Int) {

    }

    private fun Calendar.parseCalendar(): java.util.Calendar{
        return java.util.Calendar.getInstance().let {
            it.set(java.util.Calendar.YEAR,year)
            it.set(java.util.Calendar.MONTH, month - 1)
            it.set(java.util.Calendar.DAY_OF_MONTH, day)
            it
        }
    }

    override fun setupArguments(args: Bundle?) {
        primaryClassifyId = args?.getString("primaryClassifyId")?:""
        secondaryClassifyId = args?.getString("secondaryClassifyId")?:""
        testerId = args?.getString("testerId")
    }

}